﻿/*
    This file is part of nDoctor Light

    NDoctor is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.

    NDoctor is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with NDoctor.  If not, see <http://www.gnu.org/licenses/>.
*/
namespace Probel.Ldoc.Shell
{
    using System;
    using System.IO;
    using System.Linq;
    using System.Reflection;
    using System.Runtime.InteropServices;
    using System.Windows;

    using log4net;
    using log4net.Config;
    using log4net.Util;

    using Probel.Ldoc.Shell.ServiceReference;
    using Probel.Ldoc.Shell.Tools;
    using Probel.Ldoc.Shell.Views;
    using Probel.Mvvm.Gui;

    /// <summary>
    /// Interaction logic for App.xaml
    /// </summary>
    public partial class App : Application
    {
        #region Fields

        private readonly Arguments arguments = new Arguments();
        private readonly ILog Logger = LogManager.GetLogger(typeof(App));

        #endregion Fields

        #region Constructors

        public App()
        {
            this.Startup += (sender, e) =>
            {
                this.ManageArgs(e.Args);
                if (this.arguments.HookConsole) { AllocConsole(); }

                new Log4netConfigurator().Configure();

                this.SetupNetStat();
                var view = new ShellView();
                ViewService.Configure(cfg => cfg.RootWindow = view);

                var splashScreen = new SplashScreenView();
                splashScreen.Load();
                splashScreen.ShowDialog();

                view.Show();
            };

            this.DispatcherUnhandledException += (sender, e) =>
            {
                MessageBox.Show(e.Exception.ToString(), "Temporary Error Handler", MessageBoxButton.OK, MessageBoxImage.Error);
            };
        }

        #endregion Constructors

        #region Methods

        [DllImport("kernel32.dll")]
        private static extern bool AllocConsole();

        private void ManageArgs(string[] args)
        {
            this.arguments.HookConsole = (from arg in args
                                          where arg.ToLower() == "-hookconsole"
                                          select arg).Count() > 0;
        }

        private void SetupNetStat()
        {
            var version = Assembly.GetExecutingAssembly().GetName().Version.ToString();
            var os = SysInfo.Load();
            var serial = os.Serial;
            System.Threading.Tasks.Task.Run(() =>
            {
                try
                {
                    Logger.Debug("Sending statistics to the server...");
                    try
                    {
                        using (var proxy = new StatLoggerClient())
                        {
                            proxy.Register(serial, os.Version, "nDoctor Light");
                        }
                    }
                    catch (Exception ex)
                    {
                        Logger.Warn("Failed to send statistics!", ex);
                    }
                }
                catch (Exception ex)
                {
                    //Swallow the exception as Statistics are not really important. Log it anyways ;-)
                    this.Logger.Error("Error occured during statistics management.", ex);
                }
            });
        }

        #endregion Methods

        #region Nested Types

        private class Arguments
        {
            #region Properties

            public bool HookConsole
            {
                get;
                set;
            }

            #endregion Properties
        }

        #endregion Nested Types
    }
}